package com.example.his.api.mis.controller;

import cn.dev33.satoken.annotation.SaCheckLogin;
import cn.dev33.satoken.annotation.SaCheckPermission;
import cn.dev33.satoken.annotation.SaMode;
import cn.dev33.satoken.stp.StpUtil;
import cn.hutool.core.bean.BeanUtil;
import cn.hutool.core.util.ArrayUtil;
import cn.hutool.json.JSONUtil;
import com.example.his.api.common.PageUtils;
import com.example.his.api.common.R;
import com.example.his.api.db.pojo.UserEntiy;
import com.example.his.api.mis.controller.form.user.*;
import com.example.his.api.mis.service.UserService;
import org.springframework.web.bind.annotation.*;

import javax.annotation.Resource;
import javax.validation.Valid;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

@RestController
@RequestMapping("/mis/user")
public class UserController {
  
  @Resource
  private UserService userService;
  
  @PostMapping("/login")
  public R login(@RequestBody @Valid LoginForm form) {
    //    把Form对象转化成Map对象
    Map param = BeanUtil.beanToMap(form);
    //    获取登录用户的主键值
    Integer userId = userService.login(param);
    if(userId != null) {
      /**
       * 实现通断互斥效果，把该用户web端的令牌销毁
       * 在其他浏览器登录的用户就失效了，实现通断互斥
       * */
      StpUtil.logout(userId, "Web");
      
      //      通过会话对象，向satoken传递userid
      StpUtil.login(userId, "Web");
      
      //      生成新的令牌字符串，标记该令牌是给web端使用的
      String token = StpUtil.getTokenValueByLoginId(userId, "Web");
      //      获取用户权限列表
      List <String> permissions = StpUtil.getPermissionList();
      return R.ok().put("result", true).put("token", token).put("permissions", permissions);
    }
    return R.ok().put("result", false);
  }
  
  //  退出
  @GetMapping("/logout")
  @SaCheckLogin
  public R logout() {
    //    从令牌中解密出userid
    int userId = StpUtil.getLoginIdAsInt();
    //    销毁token
    StpUtil.logout(userId, "Web");
    return R.ok();
  }
  
  //  修改密码
  @PostMapping("/updatePassword")
  @SaCheckLogin
  public R updatePassword(@Valid @RequestBody UpdatePasswordForm form) {
    int userId = StpUtil.getLoginIdAsInt();
    HashMap param = new HashMap() {{
      put("userId", userId);
      put("password", form.getPassword());
      put("newPassword", form.getNewPassword());
    }};
    int rows = userService.updatePassword(param);
    
    return R.ok().put("rows", rows);
  }
  
  
  //  获取用户列表
  @PostMapping("/searchByPage")
  @SaCheckPermission(value = { "ROOT", "USER:SELECT" }, mode = SaMode.OR)
  public R searchByPage(@Valid @RequestBody SearchUserByPageForm form) {
    int page = form.getPage();
    int length = form.getLength();
    int start = (page - 1) * length;
    Map param = BeanUtil.beanToMap(form);
    param.put("start", start);
    PageUtils pageUtils = userService.searchByPage(param);
    
    return R.ok().put("page", pageUtils);
  }
  
  //  新增用户
  @PostMapping("/inster")
  @SaCheckPermission(value = { "ROOT", "USER:INSERT" }, mode = SaMode.OR)
  public R insert(@Valid @RequestBody InsertUserForm form) {
    UserEntiy user = BeanUtil.toBean(form, UserEntiy.class);
    user.setStatus(1);
    user.setRole(JSONUtil.parseArray(form.getRole()).toString());
    int rows = userService.insert(user);
    
    return R.ok().put("rows", rows);
  }
  
  //  根据用户ID查询用户信息。
  @PostMapping("/searchById")
  @SaCheckPermission(value = { "ROOT", "USER:SELECT" }, mode = SaMode.OR)
  public R searchById(@Valid @RequestBody SearchUserByIdForm from) {
    HashMap map = userService.searchById(from.getUserId());
    
    return R.ok().put("result", map);
  }
  
  //  更新用户
  @PostMapping("/update")
  @SaCheckPermission(value = { "ROOT", "USER:UPDATE" }, mode = SaMode.OR)
  public R update(@Valid @RequestBody UpdateUserFrom from) {
    
    Map param = BeanUtil.beanToMap(from);
    param.replace("role", JSONUtil.parseArray(from.getRole()).toString());
    int rows = userService.update(param);
    if(rows == 1) {
      //      修改了用户信息，将该用户所有端的应用全部退出
      StpUtil.logout(from.getUserId());
    }
    
    return R.ok().put("rows", rows);
  }
  
  
  @PostMapping("/deleteByIds")
  @SaCheckPermission(value = { "ROOT", "USER:DELETE" }, mode = SaMode.OR)
  public R deleteByIds(@Valid @RequestBody DeleteUserByIdsForm form) {
    Integer userId = StpUtil.getLoginIdAsInt();
    if(ArrayUtil.contains(form.getIds(), userId)) {
      return R.error("不能删除自己的账户");
    }
    int rows = userService.deleteByIds(form.getIds());
    if(rows > 0) {
      for(Integer id: form.getIds()) {
        //        让被删除的用户所有端应用退出
        StpUtil.logout(id);
      }
    }
    
    return R.ok().put("rows", rows);
  }
  
  @PostMapping("/dismiss")
  @SaCheckPermission(value = { "ROOT", "USER:UPDATE" }, mode = SaMode.OR)
  public R dismiss(@Valid @RequestBody DismissForm form) {
    int rows = userService.dismiss(form.getUserId());
    if(rows > 0) {
      //      让登录的离职用户退出登陆状态
      StpUtil.logout(form.getUserId().intValue());
    }
    return R.ok().put("rows", rows);
  }
  
  @PostMapping("/searchDoctorById")
  @SaCheckLogin
  public R searchDoctorById() {
    int userId = StpUtil.getLoginIdAsInt();
    HashMap map = userService.searchDoctorById(userId);
    return R.ok().put("result", map);
  }
  
  //    根据部门查找用户
  @PostMapping("/searchByDeptId")
  @SaCheckPermission(value = { "ROOT", "USER:SELECT" }, mode = SaMode.OR)
  public R searchByDeptId(@Valid @RequestBody SearchUserByDeptIdForm form) {
    int page = form.getPage();
    int length = form.getLength();
    int start = (page - 1) * length;
    Map param = BeanUtil.beanToMap(form);
    param.put("start", start);
    PageUtils pageUtils = userService.searchByDeptId(param);
    return R.ok().put("result", pageUtils);
  }
  
}
